﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Xpus.Website.Utilities;

namespace Xpus.Website.Data
{
	/// <summary>
	/// 表示区域类型。
	/// </summary>
	public class AreaType
	{
		/// <summary>
		/// 用于存放所有区域类型。
		/// </summary>
		static Dictionary<string, AreaType> _allTypes;

		const string PersonalPortalTypeName = "PersonalPortal";
		const string PersonalPageTypeName = "PersonalPage";

		/// <summary>
		/// 表示个人门户。
		/// </summary>
		public static AreaType PersonalPortal
		{
			get
			{
				return _allTypes[PersonalPortalTypeName];
			}
		}

		/// <summary>
		/// 表示个人门户页面。
		/// </summary>
		public static AreaType PersonalPage
		{
			get
			{
				return _allTypes[PersonalPageTypeName];
			}
		}

		/// <summary>
		/// 初始化区域类型。
		/// </summary>
		static AreaType()
		{
			_allTypes = new Dictionary<string, AreaType>();
			_allTypes.Add(PersonalPortalTypeName, new AreaType(PersonalPortalTypeName));
			_allTypes.Add(PersonalPageTypeName, new AreaType(PersonalPageTypeName));
		}

		/// <summary>
		/// 创建具有指定名字的区域类型。
		/// </summary>
		/// <param name="name">区域类型的名字。</param>
		private AreaType(string name)
		{
			this.Name = name;
		}

		/// <summary>
		/// 类型的名字。
		/// </summary>
		public string Name
		{
			get;
			private set;
		}

		/// <summary>
		/// 将区域类型隐式转换为字符串，表示类型的名字。
		/// </summary>
		/// <param name="type">给定的类型。</param>
		/// <returns>类型的名字。</returns>
		public static implicit operator string(AreaType type)
		{
			return type.Name;
		}

		/// <summary>
		/// 将字符串显式转换为区域类型。
		/// </summary>
		/// <param name="value">区域类型的名字。</param>
		/// <returns>名字所代表的区域类型。</returns>
		public static explicit operator AreaType(string value)
		{
			if(_allTypes.ContainsKey(value))
				return _allTypes[value];
			else
				throw new ArgumentException(string.Format(LanguageUtility.GetString("'{0}' is not a valid area type."), value), "value");
		}

		/// <summary>
		/// 判断一个名字是否为有效的区域类型名字。
		/// </summary>
		/// <param name="value">给定的名字。</param>
		/// <returns>表示是否为有效的区域类型名字。</returns>
		public static bool IsValidValue(string value)
		{
			return _allTypes.ContainsKey(value);
		}
	}

	partial class Area
	{
		#region 字段验证
		/// <summary>
		/// Type属性长度最大值。
		/// </summary>
		public const int TypeMaxLength = 32;

		/// <summary>
		/// AccessKey属性长度最大值。
		/// </summary>
		public const int AccessKeyMaxLength = 32;

		/// <summary>
		/// Title属性长度最大值。
		/// </summary>
		public const int TitleMaxLength = 256;

		/// <summary>
		/// Subtitle属性长度最大值。
		/// </summary>
		public const int SubtitleMaxLength = 256;

		/// <summary>
		/// CreatedIP属性长度最大值。
		/// </summary>
		public const int CreatedIPMaxLength = 128;

		/// <summary>
		/// Settings属性长度最大值。
		/// </summary>
		public const int SettingsMaxLength = int.MaxValue;

		partial void OnTypeChanging(string value)
		{
			FieldChecker.CheckFieldNotNull("Type", value);
			FieldChecker.CheckFieldTooLong("Type", value, TypeMaxLength);

			if(!AreaType.IsValidValue(value))
				throw new ArgumentException(
					string.Format(LanguageUtility.GetString("'{0}' is not a valid area type."), value),
					"Type");
		}

		partial void OnAccessKeyChanging(string value)
		{
			FieldChecker.CheckFieldNotNull("AccessKey", value);
			FieldChecker.CheckFieldTooLong("AccessKey", value, AccessKeyMaxLength);
		}

		partial void OnLoweredAccessKeyChanging(string value)
		{
			OnAccessKeyChanging(value);
		}

		partial void OnTitleChanging(string value)
		{
			FieldChecker.CheckFieldNotNull("Title", value);
			FieldChecker.CheckFieldTooLong("Title", value, TitleMaxLength);
		}

		partial void OnSubtitleChanging(string value)
		{
			FieldChecker.CheckFieldNotNull("Subtitle", value);
			FieldChecker.CheckFieldTooLong("Subtitle", value, SubtitleMaxLength);
		}

		partial void OnCreatedIPChanging(string value)
		{
			FieldChecker.CheckFieldNotNull("CreatedIP", value);
			FieldChecker.CheckFieldTooLong("CreatedIP", value, CreatedIPMaxLength);
		}

		partial void OnSettingsChanging(string value)
		{
			FieldChecker.CheckFieldNotNull("Settings", value);
			FieldChecker.CheckFieldTooLong("Settings", value, SettingsMaxLength);
		}
		#endregion

		#region 处理Settings属性
		SettingsUtility _theSettings = new SettingsUtility(string.Empty);

		partial void OnCreated()
		{
			this.Settings = string.Empty;
		}

		partial void OnLoaded()
		{
			_theSettings = new SettingsUtility(this.Settings);
			LoadSettings();
		}

		/// <summary>
		/// 从Settings字段中读取设置。
		/// </summary>
		internal void LoadSettings()
		{
		}

		/// <summary>
		/// 将设置保存到Settings字段中。
		/// </summary>
		internal void SaveSettings()
		{
			this.Settings = _theSettings.ToString();
		}
		#endregion
	}
}
